今天我們來看物件導向程式設計的六個原則~
原則可以把它視為是寫程式的一種好習慣~
那我們來看看這六個好習慣分別是什麼呢?
學習目標: 物件導向六個原則的概念
學習難度: ☆☆☆
第一個是 單一職責 (Single Reponsibility Principle)
單一職責原則 故名思義就是一個類別只負責一個職責~
也就是說~ 我們要讓一個類別指做一個行為~
進而讓程式形成高內聚、低耦合的狀態!
public class GameProgrammer //遊戲工程師使用遊戲引擎
{
public void coding()
{
Console.WriteLine("I could used Unity to develop game");
}
}
第二個是開閉原則(Open Closed Principle)
開閉原則是指 當我們完成一個模組(類別、方法)時,就不要在對他進行修改。
也就是說,我們在設計程式時,要盡量用擴充的方式來新增功能,而要避免用修改程式的方式。
public interface IProgrammer //工程師會寫Code
{
public Name{get;set;}
void coding();
}
public class GameProgrammer : IProgrammer //新增一個遊戲工程師
{
public Name{get;set;}
public void coding()
{
Console.WriteLine("I could used Unity to develop game");
}
}
public class DataBaseProgrammer : IProgrammer //新增一個資料庫工程師
{
public Name{get;set;}
public void coding()
{
Console.WriteLine("I could used SQL to Maintain player's data");
}
}
第三個是依賴反轉原則(Dependency-Inversion Principle)
依賴反轉原則 是指高階模組(類別、方法)不應依賴低階模組(類別、方法)~它們都應該依賴抽象。
另外~ 抽象不應該依賴於模組(類別、方法),模組(類別、方法)應該依賴抽象。
簡單來說~ 我們在設計程式時~ 要將架構設計在抽象~ 在讓模組去繼承抽象~
public interface IProgrammer
{
public Name{get;set;}
void coding();
void debug();
}
public class GameProgrammer : IProgrammer
{
public Name{get;set;}
public void coding()
{
Console.WriteLine("I could used Unity to develop game");
}
public void debug()
{
Console.WriteLine("I could debug unity program");
}
}
public class Programmer
{
private IProgrammer iprogrammer;
public Programmer(IProgrammer programmer)
{
iprogrammer = programmer;
}
public void coding()
{
iprogrammer.coding();
}
public void debug()
{
iprogrammer.debug();
}
}
class MainProgram
{
static void Main()
{
IProgrammer i_gameProgrammer = new GameProgrammer();
Programmer gameprogrammer = new Programmer(i_gameProgrammer);
gameprogrammer.coding();
gameprogrammer.debug();
}
}
第四個是里氏替換原則(Liskov Substitution Principle)
里氏替換原則是指子類別必須能夠替換父類別~
同時子類別替換父類別後,不需要改變,也不會發生任何錯誤或異常。
最簡單來說~ 父類別能做到的事情,子類別也要能做到~
public abstract class Programmer
{
public abstract void coding();
}
public class GameProgrammer : Programmer
{
public override void coding()
{
Console.WriteLine("I could used Unity to develop game");
}
}
public class DataBaseProgrammer : Programmer
{
public override void coding()
{
Console.WriteLine("I could used SQL to maintain data");
}
}
class MainProgram
{
static void Main()
{
//因為父子類能替換,所以它們能這樣實例化
Programmer gameprogrammer = new GameProgrammer();
gameprogrammer.coding();
//因為父子類能替換,所以它們能這樣實例化
Programmer databaseprogrammer = new DataBaseProgrammer();
databaseprogrammer.coding();
}
}
第五個是介面隔離原則(Interface Segregation Principle)
介面隔離原則的概念很簡單~ 就很像是單一職責的介面版本~
我們不應該在介面放入許多不同的抽象方法~ 因為有些子類別可能會難以實作~
例如~ 我們在工程師的介面放入彈鋼琴~ 但有些工程師可能不會彈鋼琴~
因此~ 那些工程師的類別就難以實現彈鋼琴的抽象方法~
所以~我們應該設計許多的介面~ 然後每個介面有它專精的抽象方法~
public interface IProgrammer
{
void coding();
}
public interface IPianoPlayer
{
void playpiano();
}
public class GameProgrammer : IProgrammer, IPianoPlayer
{
public void coding()
{
Console.WriteLine("I could used Unity to develop game");
}
public void playpiano()
{
Console.WriteLine("I could played piano");
}
}
第六個是最少知識原則(Least Knowledge Principle)
最少知識原則是指一個類別只和它相關的類別依賴~
因此~最少知識原則也要求~ 一個類別應對依賴的物件有最少的了解~
我們這次都用類別來舉例~
public class Customer
{
public Product product { get; set; }
public Customer()
{
product = new Product();
}
public void Access()
{
product.factory.FactorySecret(); //盡量不要讓顧客讀到與它無關的資料~
}
}
public class Product
{
public Factory factory { get; set; }
public Product()
{
factory = new Factory();
}
}
public class Factory
{
public void FactorySecret()
{
Console.WriteLine("This is a factory secret...");
}
}
class MainProgram
{
static void Main()
{
Customer customer = new Customer();
customer.Access(); //顧客能讀到公司的秘密,很怪吧~
}
}
參考資料:
https://dotnettutorials.net/lesson/single-responsibility-principle/
https://www.c-sharpcorner.com/UploadFile/pranayamr/open-close-principle/
https://www.youtube.com/watch?v=CxsZFL6rj5c&ab_channel=anitakumari
https://dotnettutorials.net/lesson/liskov-substitution-principle/
https://dotnettutorials.net/lesson/interface-segregation-principle/
https://www.c-sharpcorner.com/article/the-law-of-demeter/